package com.hyt.it.ogt.ykcj.job;

import com.alibaba.fastjson.JSON;
import com.hyt.it.ogt.ykcj.common.enums.CommonEnums;
import com.hyt.it.ogt.ykcj.domain.exchange.ApiLog;
import com.hyt.it.ogt.ykcj.domain.exchange.ExchangeCandidate;
import com.hyt.it.ogt.ykcj.domain.param.ApiLogQueryParam;
import com.hyt.it.ogt.ykcj.domain.vo.ExamExamineeSubjectVo;
import com.hyt.it.ogt.ykcj.service.exchange.IApiLogService;
import com.hyt.it.ogt.ykcj.service.exchange.IExchangeCandidateService;
import com.hyt.it.ogt.ykcj.service.grade.IEnterpriseExamineeInfoService;
import com.hyt.it.ogt.ykcj.utils.DateUtils;
import com.xxl.job.core.context.XxlJobHelper;
import com.xxl.job.core.handler.annotation.XxlJob;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Proxy;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * 对于同步失败的数据异步处理
 * 
 * @author huangwu
 * @since 2022-05-10
 */
@Component
@Slf4j
public class RepeatSaveCandidateInfoJob implements InitializingBean {

	@Autowired
	private IExchangeCandidateService exchangeCandidateService;
	@Autowired
	private IApiLogService apiLogService;
	@Autowired
	private IEnterpriseExamineeInfoService enterpriseExamineeInfoService;
	@Value("${repeatSaveCandidateInfo.value:}")
	private String repeatSaveCandidateInfo;

	/**
	 * 二次处理成绩系统保存失败的数据
	 */
	@XxlJob("repeatSaveCandidateInfo")
	public void repeatSaveCandidateInfo() throws Exception {
		XxlJobHelper.log("二次处理成绩数据任务开始");
		log.info("二次处理成绩数据任务开始");
		
		String xxlparam = XxlJobHelper.getJobParam(); // 执行参数
		XxlJobHelper.log("二次处理成绩数据任务xxlparam：{}", xxlparam);
		log.info("二次处理成绩数据任务xxlparam：{}", xxlparam);
		Date startTime = DateUtils.beforeOneHourToNowDate(new Date(), -24);
		Date endTime = new Date();
		String startTimeStr = "";
		String endTimeStr = "";
		try {
			if (StringUtils.isNotEmpty(xxlparam)) {
				String[] group = xxlparam.split("\\|");
				if (null != group && group.length > 1) {
					startTimeStr = group[0];
					endTimeStr = group[1];
				}
			}
		} catch (Exception e) {
			XxlJobHelper.log("error", e);
			log.info("error", e);
		}

		if (StringUtils.isNotEmpty(startTimeStr)) {
			startTime = DateUtils.parseDate(startTimeStr);
		}
		if (StringUtils.isNotEmpty(endTimeStr)) {
			endTime = DateUtils.parseDate(endTimeStr);
		}

		// 获取失败的数据
		List<ApiLog> apiLogs = new ArrayList<ApiLog>();

		boolean flag = true;
		Integer pageSize = 200;
		Integer pageNum = 1;
		ApiLogQueryParam paremApiLog = new ApiLogQueryParam();
		paremApiLog.setStatus(CommonEnums.EXCHANGE_STATUS_UNSAVE.getCode());
		paremApiLog.setQueryStartTime(startTime);
		paremApiLog.setQueryEndTime(endTime);
		while (flag) {
			try {
				List<ApiLog> apiLogsTemp = apiLogService.selectApiLogList(paremApiLog, pageNum, pageSize);
				if (CollectionUtils.isNotEmpty(apiLogsTemp)) {
					apiLogs.addAll(apiLogsTemp);
					pageNum++;
				} else {
					flag = false;
				}
			} catch (Exception e) {
				flag = false;
			}
		}

		if (CollectionUtils.isNotEmpty(apiLogs)) {
			for (ApiLog apiLog : apiLogs) {
				XxlJobHelper.log("开始计算成绩数据落库,apiLog：{}", JSON.toJSON(apiLog));
				log.info("开始计算成绩数据落库,apiLog：{}", JSON.toJSON(apiLog));
				// 把消息字符串转成对象
				try {
					ExchangeCandidate exchangeCandidate = JSON.parseObject(apiLog.getParam(), ExchangeCandidate.class);
					if (null != exchangeCandidate) {
						ExamExamineeSubjectVo examExamineeSubjectVo = exchangeCandidateService.saveCandidateInfo(exchangeCandidate);
						// 更新保存日志
						if (examExamineeSubjectVo != null && StringUtils.isNotEmpty(examExamineeSubjectVo.getExamId())) {
							enterpriseExamineeInfoService.refreshEnterpriseExamineeQualified(examExamineeSubjectVo.getExamId(), examExamineeSubjectVo.getExamineeId());
							apiLog.setStatus(CommonEnums.EXCHANGE_STATUS_SAVE.getCode());
						} else {
							apiLog.setStatus(CommonEnums.EXCHANGE_STATUS_SAVE_PART.getCode());
						}
						apiLogService.updateById(apiLog);
					}
				} catch (Exception e) {
					XxlJobHelper.log("计算成绩数据落库异常");
					XxlJobHelper.log(e);
					log.error("计算成绩数据落库异常", e);
					apiLogService.lambdaUpdate()
							.set(ApiLog::getStatus, CommonEnums.EXCHANGE_STATUS_ERROR.getCode())
							.eq(ApiLog::getId, apiLog.getId())
							.update();
				}
				XxlJobHelper.log("开始计算成绩数据落库结束-id: {}", apiLog.getId());
				log.info("开始计算成绩数据落库结束-id: {}", apiLog.getId());
			}
		}
		XxlJobHelper.log("二次处理成绩数据任务结束");
		log.info("二次处理成绩数据任务结束");
	}

	@Override
	public void afterPropertiesSet() throws Exception {
		if(!com.hyt.core.util.StringUtils.isEmpty(repeatSaveCandidateInfo)) {
			XxlJob xxlJob = this.getClass().getDeclaredMethod("repeatSaveCandidateInfo").getAnnotation(XxlJob.class);
			InvocationHandler invocationHandler = Proxy.getInvocationHandler(xxlJob);
			Field declaredField = invocationHandler.getClass().getDeclaredField("memberValues");
			declaredField.setAccessible(true);
			Map memberValues = (Map) declaredField.get(invocationHandler);
			memberValues.put("value", xxlJob.value() + repeatSaveCandidateInfo);

		}
	}
}
